﻿#include <iostream>
#include <opencv2/core.hpp>
#include <opencv2/highgui.hpp> 
#include <opencv2/imgproc.hpp>

/*
 * @brief Thresholding  二值化
**/
cv::Mat __stdcall Thresholding(const cv::Mat& img, uint8_t Threshold);

int main(int argc, char const* argv[])
{
    auto img = cv::imread("./../../images/imori.jpg", cv::IMREAD_COLOR);  // 读取方式bgr24 

    cv::Mat grayImage;
    grayImage = Thresholding(img, 128);

    cv::namedWindow("ToGray", cv::WINDOW_AUTOSIZE);
    cv::imshow("ToGray", grayImage);

    cv::waitKey(0);
    cv::destroyAllWindows();
    cv::waitKey(0);
    return 0;
}

/*
 * @brief  将图片二值化
 * @param  srcImg  转换前的图片 rgb或bgr图片都行
 * @return cv::Mat 转换后的图片
 * @note  转换公式 Y= 0.216*R+0.7152*G+0.0722*B;
 *        思路 [灰度化] 遍历所有的像素点，获取bgr的数据，通过公式转换成YUV中的Y
 *        思路 [二值化]  大于阈值 255 小于阈值 0
**/
cv::Mat Thresholding(const cv::Mat& srcImg, uint8_t Threshold)
{
    auto width = srcImg.cols;
    auto height = srcImg.rows;

    cv::Mat out = cv::Mat::zeros(height, width, CV_8UC1);  //创建一个8位1通道的图片
 
    // 转换公式 Y= 0.216*R+0.7152*G+0.0722*B;
    for (int y = 0; y < height; y++)  
    {
        for (int x = 0; x < width; x++) 
        {            
            auto R = srcImg.at<cv::Vec3b>(y, x)[2];
            auto G = srcImg.at<cv::Vec3b>(y, x)[1];
            auto B = srcImg.at<cv::Vec3b>(y, x)[0];
            auto Y = 0.216*R + 0.7152*G + 0.0722*B;
            out.at<uint8_t>(y, x) = Y > Threshold ? 255 : 0;
        }
    }

    return out;
}
